package nl.dxn.tunnel.server.ip;

import io.netty.handler.ipfilter.IpFilterRule;
import io.netty.handler.ipfilter.IpFilterRuleType;
import nl.dxn.tunnel.server.IPUtils;
import nl.dxn.tunnel.server.handel.ProxyAgentHandler;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.net.InetSocketAddress;
import java.time.LocalDateTime;
import java.time.temporal.ChronoUnit;
import java.util.*;

/**
 *
 * Ip过滤器
 *
 * @author gogym
 * @version 2019年7月13日
 * @see IpFilterRuleHandler
 * @since
 */
public class IpFilterRuleHandler implements IpFilterRule {
    private static final Logger logger = LoggerFactory.getLogger(IpFilterRuleHandler.class);
    private static final List<String> ipAllowList = new ArrayList<>();
    private static final List<String> ipDisableList = new ArrayList<>();
    private static final HashMap<String, List<LocalDateTime>> ipInMap = new HashMap<>();
    private static final HashMap<String, Integer> ipTimeMap = new HashMap<>();

    private static final List<String> blankList = Arrays.asList("218.200.153.195","119.167.77.62","121.46.248.196"
            ,"36.140.10.145","222.179.106.174","58.16.204.238");
    private static final List<String> allowProvinces = Arrays.asList("上海");


    @Override
    public boolean matches(InetSocketAddress remoteAddress) {

        //ip转成long类型
        String ip = remoteAddress.getHostString();
        if(ipAllowList.contains(ip))
        {
            return false;
        }

        if(blankList.contains(ip))
        {
            return true;
        }

        String ipRegion = IPUtils.getCityInfo(ip);
        logger.error("{} 识别 {}",ip,ipRegion);
        if(StringUtils.isBlank(ipRegion))
        {
            logger.error("{} ip未识别",ip,ipRegion);
            return true;
        }
        else
        {
            String[] splitIpInfo = ipRegion.split("\\|");
            if ("0".equals(splitIpInfo[0])){
                if ("内网IP".equals(splitIpInfo[4])){
                    logger.error("{} 内网",ip);
                    return false;
                }
                logger.error("{} 未识别 {}",ip,ipRegion);
                return true;
            }
            if (!"中国".equals(splitIpInfo[0]))
            {
                logger.error("{} 国外ip {}",ip,ipRegion);
                return true;
            }
            if ("中国".equals(splitIpInfo[0])) {
                if(!allowProvinces.contains(splitIpInfo[2]))
                {
                    logger.error("{} 非允许省份 {}",ip,ipRegion);
                    return true;
                }
            }
        }

        List<LocalDateTime> list1 = ipInMap.get(ip);
        if(list1 == null)
        {
            list1 =  new LinkedList<>();
            ipInMap.put(ip,list1);
        }

        LocalDateTime current = LocalDateTime.now();
        list1.add(current);

        if(list1.size()>4)
        {
            list1.remove(0);
            LocalDateTime first = list1.get(0);

            long loginTimes = first.until(current, ChronoUnit.SECONDS);
            if(loginTimes<=110)
            {
                logger.error("{} 上海方位110秒内超过四次 ",ip);
                list1.remove(0);
                return true;
            }
        }

        //返回false表示不执行过滤器
        return false;
    }

    @Override
    public IpFilterRuleType ruleType() {
        //返回拒绝则表示拒绝连接，反之返回接受则表示可以连接
        return IpFilterRuleType.REJECT;
    }
}